using System;
using System.Collections.Specialized;
using System.Diagnostics;
using System.Globalization;
using System.IO;
using System.Reflection;
using System.Security;
using System.Security.Permissions;
using System.Web;

namespace PickGold.Charting
{
	[AspNetHostingPermission(SecurityAction.LinkDemand, Level = AspNetHostingPermissionLevel.Minimal)]
	[AspNetHostingPermission(SecurityAction.InheritanceDemand, Level = AspNetHostingPermissionLevel.Minimal)]
	public class ChartHttpHandlerSettings
	{
		private ChartHttpHandlerStorageType _ChartImageStorage;
		private string _customHandlerName;
		private Type _customHandlerType;
		private string _directory;
		private string _folderName;
		private ConstructorInfo _handlerConstructor;
		private bool _privateImages;
		private string _sesionKey;
		private StorageSettingsCollection _ssCollection;
		private IChartStorageHandler _storageHandler;
		private TimeSpan _timeout;
		private string _url;

		internal ChartHttpHandlerSettings()
		{
			this._ssCollection = new StorageSettingsCollection();
			this._sesionKey = "chartKey-" + Guid.NewGuid().ToString("N", CultureInfo.InvariantCulture);
			this._ChartImageStorage = ChartHttpHandlerStorageType.File;
			this._timeout = TimeSpan.FromSeconds(30.0);
			this._url = "~/";
			this._directory = string.Empty;
			this._folderName = string.Empty;
			this._customHandlerName = typeof(DefaultImageHandler).FullName;
			this._privateImages = true;
		}

		internal ChartHttpHandlerSettings(string parameters)
		{
			this._ssCollection = new StorageSettingsCollection();
			this._sesionKey = "chartKey-" + Guid.NewGuid().ToString("N", CultureInfo.InvariantCulture);
			this._ChartImageStorage = ChartHttpHandlerStorageType.File;
			this._timeout = TimeSpan.FromSeconds(30.0);
			this._url = "~/";
			this._directory = string.Empty;
			this._folderName = string.Empty;
			this._customHandlerName = typeof(DefaultImageHandler).FullName;
			this._privateImages = true;
			this.ParseParams(parameters);
			this._ssCollection.SetReadOnly(true);
		}

		internal IChartStorageHandler GetHandler()
		{
			if (this._storageHandler == null)
			{
				if (this._handlerConstructor == null)
				{
					this.InspectHandlerLoader();
				}
				this._storageHandler = this._handlerConstructor.Invoke(new object[0]) as IChartStorageHandler;
			}
			return this._storageHandler;
		}

		internal void Inspect()
		{
			switch (this.StorageType)
			{
				case ChartHttpHandlerStorageType.File:
					if (!IsWebDevActive() || (string.Compare(this["WebDevServerUseConfigSettings"], "true", StringComparison.OrdinalIgnoreCase) == 0))
					{
						if (string.IsNullOrEmpty(this.Url))
						{
							throw new ArgumentException(SR.ExceptionHttpHandlerUrlMissing);
						}
						string directory = this.Directory;
						if (string.IsNullOrEmpty(directory))
						{
							try
							{
								directory = HttpContext.Current.Server.MapPath(this.Url);
							}
							catch (Exception exception)
							{
								throw new InvalidOperationException(SR.ExceptionHttpHandlerUrlInvalid, exception);
							}
						}
						directory = directory.Replace("/", @"\");
						if (!directory.EndsWith(@"\", StringComparison.Ordinal))
						{
							directory = directory + @"\";
						}
						if (!System.IO.Directory.Exists(directory))
						{
							throw new DirectoryNotFoundException(SR.ExceptionHttpHandlerTempDirectoryInvalid(directory));
						}
						Exception exception2 = null;
						try
						{
							string path = directory + Guid.NewGuid().ToString("N", CultureInfo.InvariantCulture);
							using (File.Create(path))
							{
							}
							File.Delete(path);
						}
						catch (DirectoryNotFoundException exception3)
						{
							exception2 = exception3;
						}
						catch (NotSupportedException exception4)
						{
							exception2 = exception4;
						}
						catch (PathTooLongException exception5)
						{
							exception2 = exception5;
						}
						catch (UnauthorizedAccessException exception6)
						{
							exception2 = exception6;
						}
						if (exception2 != null)
						{
							throw new UnauthorizedAccessException(SR.ExceptionHttpHandlerTempDirectoryUnaccesible(directory));
						}
						this.Directory = directory;
						break;
					}
					this.StorageType = ChartHttpHandlerStorageType.Process;
					break;
			}
			if (!string.IsNullOrEmpty(this.CustomHandlerName))
			{
				this.InspectHandlerLoader();
			}
		}

		private void InspectHandlerLoader()
		{
			this._handlerConstructor = this.HandlerType.GetConstructor(BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance, null, new Type[0], new ParameterModifier[0]);
			if (this._handlerConstructor == null)
			{
				throw new InvalidOperationException(SR.ExceptionHttpHandlerCanNotLoadType(this.HandlerType.FullName));
			}
			if (this.GetHandler() == null)
			{
				throw new InvalidOperationException(SR.ExceptionHttpHandlerImageHandlerInterfaceUnsupported(ChartHttpHandler.Settings.HandlerType.FullName));
			}
		}

		private static bool IsWebDevActive()
		{
			try
			{
				if (Process.GetCurrentProcess().ProcessName.StartsWith("WebDev.WebServer", StringComparison.OrdinalIgnoreCase))
				{
					return true;
				}
			}
			catch (SecurityException)
			{
			}
			return false;
		}

		private void ParseParams(string parameters)
		{
			if (!string.IsNullOrEmpty(parameters))
			{
				string[] strArray = parameters.Split(new char[] { ';' }, StringSplitOptions.RemoveEmptyEntries);
				for (int i = 0; i < strArray.Length; i++)
				{
					string str = strArray[i].Trim();
					int index = str.IndexOf('=');
					if (index != -1)
					{
						string name = str.Substring(0, index).Trim();
						string str3 = str.Substring(index + 1).Trim();
						this._ssCollection.Add(name, str3);
						if (name.StartsWith("stor", StringComparison.OrdinalIgnoreCase))
						{
							if (!str3.StartsWith("inproc", StringComparison.OrdinalIgnoreCase) && !str3.StartsWith("memory", StringComparison.OrdinalIgnoreCase))
							{
								if (!str3.StartsWith("file", StringComparison.OrdinalIgnoreCase))
								{
									if (!str3.StartsWith("session", StringComparison.OrdinalIgnoreCase))
									{
										throw new ArgumentException(SR.ExceptionHttpHandlerParameterUnknown(name, str3));
									}
									this.StorageType = ChartHttpHandlerStorageType.Cache;
								}
								else
								{
									this.StorageType = ChartHttpHandlerStorageType.File;
								}
							}
							else
							{
								this.StorageType = ChartHttpHandlerStorageType.Process;
							}
						}
						else if (name.StartsWith("url", StringComparison.OrdinalIgnoreCase))
						{
							if (!str3.EndsWith("/", StringComparison.Ordinal))
							{
								str3 = str3 + "/";
							}
							this.Url = str3;
						}
						else if (name.StartsWith("dir", StringComparison.OrdinalIgnoreCase))
						{
							this.Directory = str3;
						}
						else
						{
							if (name.StartsWith("time", StringComparison.OrdinalIgnoreCase))
							{
								try
								{
									int num3 = int.Parse(str3, CultureInfo.InvariantCulture);
									if (num3 < -1)
									{
										throw new ArgumentException(SR.ExceptionHttpHandlerValueInvalid);
									}
									if (num3 == -1)
									{
										this.Timeout = TimeSpan.MaxValue;
									}
									else
									{
										this.Timeout = TimeSpan.FromSeconds((double)num3);
									}
									goto Label_01E0;
								}
								catch (Exception exception)
								{
									throw new ArgumentException(SR.ExceptionHttpHandlerTimeoutParameterInvalid, exception);
								}
							}
							if (name.StartsWith("handler", StringComparison.OrdinalIgnoreCase))
							{
								this.CustomHandlerName = str3;
							}
							else if (name.StartsWith("privateImages", StringComparison.OrdinalIgnoreCase))
							{
								bool result = true;
								if (bool.TryParse(str3, out result))
								{
									this._privateImages = result;
								}
							}
						Label_01E0: ;
						}
					}
				}
			}
			this.Inspect();
		}

		internal void PrepareDesignTime()
		{
			this.StorageType = ChartHttpHandlerStorageType.File;
			this.Timeout = TimeSpan.FromSeconds(3.0);
			this.Url = Path.GetTempPath();
			this.Directory = Path.GetTempPath();
		}

		internal void ValidateUri(string key)
		{
			if (this.StorageType == ChartHttpHandlerStorageType.File)
			{
				Uri objA = new Uri(this.Directory);
				Uri objB = new Uri(this.Directory + Path.GetDirectoryName(key) + @"\");
				if (!object.Equals(objA, objB) && !objA.IsBaseOf(objB))
				{
					throw new UnauthorizedAccessException(SR.ExceptionHttpHandlerInvalidLocation);
				}
			}
		}

		public string CustomHandlerName
		{
			get
			{
				return this._customHandlerName;
			}
			set
			{
				this._customHandlerName = value;
			}
		}

		internal bool DeleteAfterServicing
		{
			get
			{
				return (string.Compare(this["DeleteAfterServicing"], "false", StringComparison.OrdinalIgnoreCase) != 0);
			}
		}

		public string Directory
		{
			get
			{
				return this._directory;
			}
			set
			{
				this._directory = value;
			}
		}

		public string FolderName
		{
			get
			{
				return this._folderName;
			}
			set
			{
				if (!string.IsNullOrEmpty(value))
				{
					if (!value.EndsWith("/", StringComparison.Ordinal) && !value.EndsWith(@"\", StringComparison.Ordinal))
					{
						value = value + @"\";
					}
					this.ValidateUri(value);
				}
				this._folderName = value;
			}
		}

		public Type HandlerType
		{
			get
			{
				if (this._customHandlerType == null)
				{
					this._customHandlerType = Type.GetType(this.CustomHandlerName, true);
				}
				return this._customHandlerType;
			}
		}

		public string this[string name]
		{
			get
			{
				return this._ssCollection[name];
			}
		}

		public bool PrivateImages
		{
			get
			{
				return this._privateImages;
			}
		}

		internal string SessionID
		{
			get
			{
				if (HttpContext.Current != null)
				{
					if (HttpContext.Current.User.Identity.IsAuthenticated)
					{
						return HttpContext.Current.User.Identity.Name;
					}
					if (!string.IsNullOrEmpty(HttpContext.Current.Request.AnonymousID))
					{
						return HttpContext.Current.Request.AnonymousID;
					}
					if (HttpContext.Current.Session != null)
					{
						if (HttpContext.Current.Session.IsNewSession)
						{
							if (HttpContext.Current.Session.IsReadOnly)
							{
								return string.Empty;
							}
							HttpContext.Current.Session[this._sesionKey] = 0;
						}
						return HttpContext.Current.Session.SessionID;
					}
				}
				return string.Empty;
			}
		}

		public ChartHttpHandlerStorageType StorageType
		{
			get
			{
				return this._ChartImageStorage;
			}
			set
			{
				this._ChartImageStorage = value;
			}
		}

		public TimeSpan Timeout
		{
			get
			{
				return this._timeout;
			}
			set
			{
				this._timeout = value;
			}
		}

		public string Url
		{
			get
			{
				return this._url;
			}
			set
			{
				this._url = value;
			}
		}

		private class StorageSettingsCollection : NameValueCollection
		{
			internal void SetReadOnly(bool flag)
			{
				base.IsReadOnly = flag;
			}
		}
	}
}

